<?php
#
# dmBridge: a data access framework for CONTENTdm(R)
#
# Copyright © 2009, 2010, 2011 Board of Regents of the Nevada System of Higher
# Education, on behalf of the University of Nevada, Las Vegas
#

/**
 * @author Alex Dolski <alex.dolski@unlv.edu>
 * @author Eric Celeste <efc@clst.org>
 * @license http://www.opensource.org/licenses/mit-license.php
 */

// let's make sure the $_SERVER['DOCUMENT_ROOT'] variable is set, even in IIS
if (!isset($_SERVER['DOCUMENT_ROOT'])) {
	if (isset($_SERVER['SCRIPT_FILENAME'])) {
		$_SERVER['DOCUMENT_ROOT'] = str_replace(
			'\\',
			'/',
			substr($_SERVER['SCRIPT_FILENAME'], 0, 0-strlen($_SERVER['PHP_SELF']))
		);
	} else if (isset($_SERVER['PATH_TRANSLATED'])) {
		$_SERVER['DOCUMENT_ROOT'] = str_replace(
			'\\', '/',
			substr(
				str_replace('\\\\', '\\', $_SERVER['PATH_TRANSLATED']),
				0,
				0-strlen($_SERVER['PHP_SELF'])
			)
		);
	}
}

// in a PHP command-line environment, it still will not be set. So, set it.
if (!$_SERVER['DOCUMENT_ROOT']) {
	$_SERVER['DOCUMENT_ROOT'] = realpath(dirname(__FILE__) . "/../../..");
}

/* We use our own autoloader, to avoid conflicting with any other that may
be defined. */
spl_autoload_register('dmAutoloader');

function dmAutoloader($class) {
	$prefix = dirname(__FILE__) . "/../../";
	// this should be a lot faster than a directory scan
	$all_classes = array(
		'content_negotiation' => 'system/libraries/content_negotiation',
		'DMAbstractAuthenticationService' => 'system/user',
		'DMAbstractController' => 'system/controllers',
		'DMAbstractDataStoreQuery' => 'system/query',
		'DMAbstractDMBridgeModule' => 'system/module',
		'DMAbstractForm' => 'system/form',
		'DMAbstractFormField' => 'system/form',
		'DMAbstractQuery' => 'system/query',
		'DMAbstractRepresentationTransformer' => 'system/http',
		'DMAbstractSocialDataQuery' => 'system/query',
		'DMAbstractSocialEntity' => 'system/models',
		'DMAbstractTemplateHelper' => 'system/template',
		'DMAbstractView' => 'system/views',
		'DMAbstractViewer' => 'system/viewers',
		'DMAPICollectionController' => 'system/controllers',
		'DMAPICommentController' => 'system/controllers',
		'DMAPIDocumentationController' => 'system/controllers',
		'DMAPIObjectController' => 'system/controllers',
		'DMAPISchemaController' => 'system/controllers',
		'DMAPISettingController' => 'system/controllers',
		'DMAPIStatusController' => 'system/controllers',
		'DMAPITagController' => 'system/controllers',
		'DMAPIVocabularyController' => 'system/controllers',
		'DMAbstractController' => 'system/controllers',
		'DMAtomRepresentationTransformer' => 'system/http',
		'DMAuthenticationService' => 'system/user',
		'DMAuthenticationServiceFactory' => 'system/user',
		'DMBridgeComponent' => 'system',
		'DMBridgeControlPanelModule' => 'system/module',
		'DMBridgeDataStoreModule' => 'system/module',
		'DMBridgeModule' => 'system/module',
		'DMBridgeRepresentationSchemaModule' => 'system/module',
		'DMBridgeTemplateHelperModule' => 'system/module',
		'DMBridgeVersion' => 'system',
		'DMCdmAuthenticationService' => 'system/user',
		'DMCheckboxField' => 'system/form',
		'DMClassNotFoundException' => 'system/exceptions',
		'DMCollection' => 'system/models',
		'DMCollectionFactory' => 'system/models',
		'DMComment' => 'system/models',
		'DMCommentQuery' => 'system/query',
		'DMConfigIni' => 'system/config',
		'DMConfigXML' => 'system/config',
		'DMConstraintException' => 'system/exceptions',
		'DMControlPanelTemplateHelper' => 'system/template',
		'DMControlPanelView' => 'system/views',
		'DMCustomTemplateHelper' => 'system/template',
		'DMCPAdminController' => 'system/controllers',
		'DMCPBasicController' => 'system/controllers',
		'DMCPBasicSettingsForm' => 'system/controllers/forms',
		'DMCPCollectionController' => 'system/controllers',
		'DMCPCommentController' => 'system/controllers',
		'DMCPCommentSettingsForm' => 'system/controllers/forms',
		'DMCPCQRController' => 'system/controllers',
		'DMCPDataStoreConfigureView' => 'system/views',
		'DMCPEditCollectionForm' => 'system/controllers/forms',
		'DMCPFeedController' => 'system/controllers',
		'DMCPFeedSettingsForm' => 'system/controllers/forms',
		'DMCPMenuItem' => 'system/control_panel',
		'DMCPMenuSection' => 'system/control_panel',
		'DMCPModuleController' => '/system/controllers',
		'DMCPRatingController' => 'system/controllers',
		'DMCPRatingSettingsForm' => 'system/controllers/forms',
		'DMCPReferenceURLController' => 'system/controllers',
		'DMCPTagController' => 'system/controllers',
		'DMCPTagSettingsForm' => 'system/controllers/forms',
		'DMCPTemplateController' => 'system/controllers',
		'DMCPTemplateSetForm' => 'system/controllers/forms',
		'DMDataStore' => 'system/data',
		'DMDataStoreException' => 'system/data',
		'DMDataStoreQuery' => 'system/query',
		'DMDataStoreFactory' => 'system/data',
		'DMDataStoreType' => 'system/data',
		'DMDateTime' => 'system/util',
		'DMDCElement' => 'system/models',
		'DMDOMDocument' => 'system/util',
		'DMEmailMessage' => 'system/mail',
		'DMErrorException' => 'system/exceptions',
		'DMException' => 'system/exceptions',
		'DMExternalView' => 'system/views',
		'DMFacetTerm' => 'system/models',
		'DMFavoriteQuery' => 'system/query',
		'DMFavoritesTemplateHelper' => 'system/template',
		'DMFavoritesView' => 'system/views',
		'DMFeedRepresentationTransformer' => 'system/http',
		'DMFile' => 'system/util',
		'DMFileLinkViewer' => 'system/viewers/DMFileLinkViewer',
		'DMFileNotFoundException' => 'system/util',
		'DMFlash' => 'system/template',
		'DMFormField' => 'system/form',
		'DMFormFieldType' => 'system/form',
		'DMGenericImageViewer' => 'system/viewers/DMGenericImageViewer',
		'DMGenericObjectViewer' => 'system/viewers/DMGenericObjectViewer',
		'DMGenericPDFViewer' => 'system/viewers/DMGenericPDFViewer',
		'DMGenericTemplateHelper' => 'system/template',
		'DMHiddenField' => 'system/form',
		'DMHTTPAPIRepresentationTransformer' => 'system/http',
		'DMHTTPClient' => 'system/http',
		'DMHTTPResponseFactory' => 'system/http',
		'DMHTTPMessage' => 'system/http',
		'DMHTTPMethod' => 'system/http',
		'DMHTTPRepresentation' => 'system/http',
		'DMHTTPRequest' => 'system/http',
		'DMHTTPResponse' => 'system/http',
		'DMHTTPResponseFactory' => 'system/http',
		'DMIllegalArgumentException' => 'system/exceptions',
		'DMInput' => 'system/query',
		'DMInternalErrorException' => 'system/exceptions',
		'DMInternalURI' => 'system/http',
		'DMInternalView' => 'system/views',
		'DMIntroController' => 'system/controllers',
		'DMInvalidEmailException' => 'system/mail',
		'DMInvalidRouteException' => 'system/http',
		'DMIOException' => 'system/exceptions',
		'DMJSONRepresentationTransformer' => 'system/http',
		'DMJSONRepresentationTransformerV1' => 'system/http',
		'DMJSONPRepresentationTransformerV1' => 'system/http',
		'DMLanguage' => 'system/util',
		'DMLocalizedString' => 'system/util',
		'DMLogEntry' => 'system/logging',
		'DMLoggable' => 'system/logging',
		'DMLogger' => 'system/logging',
		'DMLoginView' => 'system/views',
		'DMMailable' => 'system/mail',
		'DMMailer' => 'system/mail',
		'DMMediaType' => 'system/util',
		'DMModel' => 'system/models',
		'DMMonocleViewer' => 'system/viewers/DMMonocleViewer',
		'DMMonocle2Viewer' => 'system/viewers/DMMonocle2Viewer',
		'DMModuleActivationException' => 'system/module',
		'DMModuleManager' => 'system/module',
		'DMMySQLDataStore' => 'system/data',
		'DMNewsItem' => 'system/control_panel',
		'DMNoSuchFieldException' => 'system/exceptions',
		'DMNoSuchMethodException' => 'system/exceptions',
		'DMNullViewer' => 'system/viewers',
		'DMObject' => 'system/models',
		'DMObjectCommentForm' => 'system/controllers/forms',
		'DMObjectFactory' => 'system/models',
		'DMObjectQuery' => 'system/query',
		'DMObjectResultsTemplateHelper' => 'system/template',
		'DMObjectResultsView' => 'system/views',
		'DMObjectTemplateHelper' => 'system/template',
		'DMObjectView' => 'system/views',
		'DMObjectViewerDefinition' => 'system/viewers',
		'DMObjectViewerDelegate' => 'system/viewers',
		'DMObjectViewerDelegateManager' => 'system/viewers',
		'DMPaginatedPDFViewer' => 'system/viewers/DMPaginatedPDFViewer',
		'DMPDFFile' => 'system/util',
		'DMRepresentationFactory' => 'system/http',
		'DMPasswordField' => 'system/form',
		'DMPDODataStore' => 'system/data',
		'DMPDOException' => 'system/data',
		'DMQuery' => 'system/query',
		'DMQueryPredicate' => 'system/query',
		'DMQuickTimeViewer' => 'system/viewers/DMQuickTimeViewer',
		'DMRadioField' => 'system/form',
		'DMRating' => 'system/models',
		'DMResultsTemplateHelper' => 'system/template',
		'DMResultsView' => 'system/views',
		'DMRoute' => 'system/http',
		'DMSearchTemplateHelper' => 'system/template',
		'DMSearchView' => 'system/views',
		'DMSecurityException' => 'system/exceptions',
		'DMSelectField' => 'system/form',
		'DMSession' => 'system/http',
		'DMShellCommand' => 'system/util',
		'DMSitemapRepresentationTransformer' => 'system/http',
		'DMSocialEntity' => 'system/models',
		'DMSQLiteDataStore' => 'system/data',
		'DMString' => 'system/util',
		'DMSystemErrorTemplateHelper' => 'system/template',
		'DMSystemErrorView' => 'system/views',
		'DMTag' => 'system/models',
		'DMTagForm' => 'system/controllers/forms',
		'DMTagQuery' => 'system/query',
		'DMTEFavoriteController' => 'system/controllers',
		'DMTEObjectController' => 'system/controllers',
		'DMTESearchController' => 'system/controllers',
		'DMTESitemapController' => 'system/controllers',
		'DMTEUserController' => 'system/controllers',
		'DMTemplate' => 'system/template',
		'DMTemplateEngineView' => 'system/views',
		'DMTemplateHelper' => 'system/template',
		'DMTemplateSet' => 'system/template',
		'DMTEObjectController' => 'system/controllers',
		'DMTESearchController' => 'system/controllers',
		'DMTESitemapController' => 'system/controllers',
		'DMTEUserController' => 'system/controllers',
		'DMTextareaField' => 'system/form',
		'DMTextField' => 'system/form',
		'DMUpdateManager' => 'system/control_panel',
		'DMUnavailableModelException' => 'system/models',
		'DMURI' => 'system/http',
		'DMURIAddressable' => 'system/models',
		'DMUser' => 'system/user',
		'DMXMLRepresentationTransformer' => 'system/http',
		'DMXMLRepresentationTransformerV1' => 'system/http'
	);

	if (array_key_exists($class, $all_classes)) {
		$path = $prefix . $all_classes[$class] . "/" . $class . ".php";
		if (file_exists($path)) {
			include_once($path);
			return;
		}
	}

	// not found in table; scan the relevant places in the filesystem as a
	// last resort
	$it = new RecursiveDirectoryIterator($prefix . 'extensions/viewers');
	foreach (new RecursiveIteratorIterator($it) as $filename) {
		$info = pathinfo($filename);
		if (!array_key_exists("extension", $info)) {
			continue;
		}
		// skip hidden folders, such as .svn
		if (strpos($info['dirname'], "/.") !== false) {
			continue;
		}
		$classname = basename($filename, "." . $info['extension']);
		if (strtolower($classname) == strtolower($class)) {
			include_once($filename);
			return;
		}
	}
}

// include cdm library files
$root = DMConfigIni::getInstance()->getString("contentdm.php_api.pathname");
$dmimage = sprintf("%s/%s/DMImage.php",
	$_SERVER['DOCUMENT_ROOT'],
	trim($root, "/"));
$dmsystem = sprintf("%s/%s/DMSystem.php",
	$_SERVER['DOCUMENT_ROOT'],
	trim($root, "/"));

if (!include_once($dmimage)) {
	header("HTTP/1.1 500 Internal Server Error");
	die("Unable to load DMImage.php; check the setting of "
			. "contentdm.php_api.pathname in config.ini.");
}
if (!include_once($dmsystem)) {
	header("HTTP/1.1 500 Internal Server Error");
	die("Unable to load DMSystem.php; check the setting of "
			. "contentdm.php_api.pathname in config.ini.");
}

/**
 * Assists in debugging; extract the important parts from debug_backtrace()
 * without printing the entire object graph
 */
function backtrace() {
	$pretty = "";
	foreach (debug_backtrace() as $line) {
		$pretty .= sprintf("%s::%s() (%s:%d)<br/>\n",
				array_key_exists("class", $line) ? $line['class'] : "",
				$line['function'],
				$line['file'],
				$line['line']);
	}
	return $pretty;
}